<?php
declare(strict_types=1);

/**
 * Created by PhpStorm.
 * User: 小灰灰
 * Date: 2023-02-22
 * Time: 9:45:22
 * Info:
 */

namespace app\common\model;

use app\common\service\admin\AuthService;
use think\facade\Db;
use think\Model;

class Admin extends TimeInit
{

    /**
     * logintime 获取器，自动格式化时间戳为日期时间字符串
     *
     * @param mixed $value
     *
     * @return string
     */
    public function getLogintimeAttr($value): string
    {
        if (empty($value)) {
            return '';
        }

        return date('Y-m-d H:i:s', (int)$value);
    }

    /**
     * 获取管理员列表
     *
     * @param array $params
     *
     * @return array
     * @throws \think\db\exception\DataNotFoundException
     * @throws \think\db\exception\DbException
     * @throws \think\db\exception\ModelNotFoundException
     */
    public static function getAdminList(array $params = []): array
    {
        if (empty($params)) {
            return ['list' => [], 'count' => 0];
        }

        // 提取参数
        $limit = (int)($params['limit'] ?? 10);
        $first = (int)($params['first'] ?? 0);
        $field = $params['field'] ?? 'id';
        $order = $params['order'] ?? 'asc';
        $key   = $params['key'] ?? [];

        // 获取当前管理员权限范围
        $childrenAdminIds = AuthService::getChildrenAdminIds(true);

        if (empty($childrenAdminIds)) {
            return ['list' => [], 'count' => 0];
        }

        // 构建查询条件
        $query = self::where('id', 'in', $childrenAdminIds);

        // 用户名筛选
        if ( ! empty($key['username'])) {
            $query->whereLike('username', '%'.$key['username'].'%');
        }

        // 角色筛选
        if ( ! empty($key['role_id'])) {
            $uids = AuthGroupAccess::where('group_id', $key['role_id'])->column('uid');
            if ( ! empty($uids)) {
                $query->whereIn('id', $uids);
            } else {
                // 如果没有匹配的用户，直接返回空结果
                return ['list' => [], 'count' => 0];
            }
        }

        // 状态筛选
        if (isset($key['status']) && $key['status'] !== '') {
            $query->where('status', $key['status']);
        }

        // 获取总数
        $count = $query->count();

        if ($count === 0) {
            return ['list' => [], 'count' => 0];
        }

        // 获取列表数据
        $list = $query->limit($first, $limit)->order($field, $order)->select();

        if ( ! $list->isEmpty()) {
            // 批量获取用户组信息，避免N+1查询
            $adminIds  = $list->column('id');
            $groupData = self::getAdminGroupData($adminIds);

            // 处理列表数据
            foreach ($list as $item) {
                $item['group_name'] = $groupData[$item['id']] ?? '';
            }
        }

        return [
            'list'  => $list->toArray(),
            'count' => (int)$count
        ];
    }

    /**
     * 批量获取管理员用户组信息
     *
     * @param array $adminIds
     *
     * @return array
     */
    private static function getAdminGroupData(array $adminIds): array
    {
        $result = [];

        // 批量获取所有管理员的用户组
        $groupAccessList = AuthGroupAccess::whereIn('uid', $adminIds)->select();
        $groupIds        = array_unique($groupAccessList->column('group_id'));

        if (empty($groupIds)) {
            foreach ($adminIds as $adminId) {
                $result[$adminId] = '';
            }

            return $result;
        }

        // 批量获取用户组名称
        $groupNames = AuthGroup::whereIn('id', $groupIds)->column('name', 'id');

        // 按管理员ID分组用户组
        $adminGroups = [];
        foreach ($groupAccessList as $access) {
            $groupId = $access['group_id'];
            if (isset($groupNames[$groupId])) {
                $adminGroups[$access['uid']][] = $groupNames[$groupId];
            }
        }

        // 组装结果
        foreach ($adminIds as $adminId) {
            $result[$adminId] = isset($adminGroups[$adminId]) ? implode(',', $adminGroups[$adminId]) : '';
        }

        return $result;
    }

    /**
     * 更新后台登录失败次数
     *
     * @param int $adminId
     * @param int $failure
     *
     * @return bool
     */
    public static function editLoginFailure(int $adminId, int $failure = 0): bool
    {
        if (empty($adminId)) {
            return false;
        }

        $currentTime = time();

        if ($failure) {
            // 增加失败次数
            return (bool)self::where(['id' => $adminId])->update([
                'logintime'     => $currentTime,
                'update_time'   => $currentTime,
                'login_failure' => Db::raw('login_failure+1')
            ]);
        } else {
            // 重置失败次数
            return (bool)self::where(['id' => $adminId])->update([
                'login_failure' => 0,
                'update_time'   => $currentTime
            ]);
        }
    }

    /**
     * 批量更新登录失败次数
     *
     * @param array $adminIds
     * @param int   $failure
     *
     * @return int 影响的行数
     */
    public static function batchEditLoginFailure(array $adminIds, int $failure = 0): int
    {
        if (empty($adminIds)) {
            return 0;
        }

        $currentTime = time();

        if ($failure) {
            // 批量增加失败次数
            return self::whereIn('id', $adminIds)->update([
                'logintime'     => $currentTime,
                'update_time'   => $currentTime,
                'login_failure' => Db::raw('login_failure+1')
            ]);
        } else {
            // 批量重置失败次数
            return self::whereIn('id', $adminIds)->update([
                'login_failure' => 0,
                'update_time'   => $currentTime
            ]);
        }
    }
}
